home *** CD-ROM | disk | FTP | other *** search
/ Chip 2007 January, February, March & April / Chip-Cover-CD-2007-02.iso / Pakiet bezpieczenstwa / mini Pentoo LiveCD 2006.1 / mpentoo-2006.1.iso / livecd.squashfs / usr / lib / mozilla-firefox / include / string / nsTString.h < prev    next >
C/C++ Source or Header  |  2006-05-08  |  25KB  |  724 lines

  1. /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
  2. /* vim:set ts=2 sw=2 sts=2 et cindent: */
  3. /* ***** BEGIN LICENSE BLOCK *****
  4.  * Version: MPL 1.1/GPL 2.0/LGPL 2.1
  5.  *
  6.  * The contents of this file are subject to the Mozilla Public License Version
  7.  * 1.1 (the "License"); you may not use this file except in compliance with
  8.  * the License. You may obtain a copy of the License at
  9.  * http://www.mozilla.org/MPL/
  10.  *
  11.  * Software distributed under the License is distributed on an "AS IS" basis,
  12.  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
  13.  * for the specific language governing rights and limitations under the
  14.  * License.
  15.  *
  16.  * The Original Code is Mozilla.
  17.  *
  18.  * The Initial Developer of the Original Code is IBM Corporation.
  19.  * Portions created by IBM Corporation are Copyright (C) 2003
  20.  * IBM Corporation. All Rights Reserved.
  21.  *
  22.  * Contributor(s):
  23.  *   Rick Gessner <rickg@netscape.com> (original author)
  24.  *   Scott Collins <scc@mozilla.org>
  25.  *   Darin Fisher <darin@meer.net>
  26.  *
  27.  * Alternatively, the contents of this file may be used under the terms of
  28.  * either the GNU General Public License Version 2 or later (the "GPL"), or
  29.  * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
  30.  * in which case the provisions of the GPL or the LGPL are applicable instead
  31.  * of those above. If you wish to allow use of your version of this file only
  32.  * under the terms of either the GPL or the LGPL, and not to allow others to
  33.  * use your version of this file under the terms of the MPL, indicate your
  34.  * decision by deleting the provisions above and replace them with the notice
  35.  * and other provisions required by the GPL or the LGPL. If you do not delete
  36.  * the provisions above, a recipient may use your version of this file under
  37.  * the terms of any one of the MPL, the GPL or the LGPL.
  38.  *
  39.  * ***** END LICENSE BLOCK ***** */
  40.  
  41.  
  42.   /**
  43.    * This is the canonical null-terminated string class.  All subclasses
  44.    * promise null-terminated storage.  Instances of this class allocate
  45.    * strings on the heap.
  46.    *
  47.    * This class is also known as nsAFlat[C]String, where "flat" is used
  48.    * to denote a null-terminated string.
  49.    */
  50. class nsTString_CharT : public nsTSubstring_CharT
  51.   {
  52.     public:
  53.  
  54.       typedef nsTString_CharT    self_type;
  55.  
  56.     public:
  57.  
  58.         /**
  59.          * constructors
  60.          */
  61.  
  62.       nsTString_CharT()
  63.         : substring_type() {}
  64.  
  65.       explicit
  66.       nsTString_CharT( char_type c )
  67.         : substring_type()
  68.         {
  69.           Assign(c);
  70.         }
  71.  
  72.       explicit
  73.       nsTString_CharT( const char_type* data, size_type length = size_type(-1) )
  74.         : substring_type()
  75.         {
  76.           Assign(data, length);
  77.         }
  78.  
  79.       nsTString_CharT( const self_type& str )
  80.         : substring_type()
  81.         {
  82.           Assign(str);
  83.         }
  84.  
  85.       nsTString_CharT( const substring_tuple_type& tuple )
  86.         : substring_type()
  87.         {
  88.           Assign(tuple);
  89.         }
  90.  
  91.       explicit
  92. #ifdef MOZ_V1_STRING_ABI
  93.       nsTString_CharT( const abstract_string_type& readable )
  94. #else
  95.       nsTString_CharT( const substring_type& readable )
  96. #endif
  97.         : substring_type()
  98.         {
  99.           Assign(readable);
  100.         }
  101.  
  102.  
  103.         // |operator=| does not inherit, so we must define our own
  104.       self_type& operator=( char_type c )                                                       { Assign(c);        return *this; }
  105.       self_type& operator=( const char_type* data )                                             { Assign(data);     return *this; }
  106.       self_type& operator=( const self_type& str )                                              { Assign(str);      return *this; }
  107.       self_type& operator=( const substring_type& str )                                         { Assign(str);      return *this; }
  108.       self_type& operator=( const substring_tuple_type& tuple )                                 { Assign(tuple);    return *this; }
  109. #ifdef MOZ_V1_STRING_ABI
  110.       self_type& operator=( const abstract_string_type& readable )                              { Assign(readable); return *this; }
  111. #endif
  112.  
  113.  
  114.         /**
  115.          * returns the null-terminated string
  116.          */
  117.  
  118.       const char_type* get() const
  119.         {
  120.           return mData;
  121.         }
  122.  
  123.  
  124.         /**
  125.          * returns character at specified index.
  126.          *         
  127.          * NOTE: unlike nsTSubstring::CharAt, this function allows you to index
  128.          *       the null terminator character.
  129.          */
  130.  
  131.       char_type CharAt( index_type i ) const
  132.         {
  133.           NS_ASSERTION(i <= mLength, "index exceeds allowable range");
  134.           return mData[i];
  135.         }
  136.  
  137.       char_type operator[]( index_type i ) const
  138.         {
  139.           return CharAt(i);
  140.         }
  141.  
  142.  
  143. #if MOZ_STRING_WITH_OBSOLETE_API
  144.  
  145.  
  146.         /**
  147.          *  Search for the given substring within this string.
  148.          *  
  149.          *  @param   aString is substring to be sought in this
  150.          *  @param   aIgnoreCase selects case sensitivity
  151.          *  @param   aOffset tells us where in this string to start searching
  152.          *  @param   aCount tells us how far from the offset we are to search. Use
  153.          *           -1 to search the whole string.
  154.          *  @return  offset in string, or kNotFound
  155.          */
  156.  
  157.       NS_COM PRInt32 Find( const nsCString& aString, PRBool aIgnoreCase=PR_FALSE, PRInt32 aOffset=0, PRInt32 aCount=-1 ) const;
  158.       NS_COM PRInt32 Find( const char* aString, PRBool aIgnoreCase=PR_FALSE, PRInt32 aOffset=0, PRInt32 aCount=-1 ) const;
  159.  
  160. #ifdef CharT_is_PRUnichar
  161.       NS_COM PRInt32 Find( const nsAFlatString& aString, PRInt32 aOffset=0, PRInt32 aCount=-1 ) const;
  162.       NS_COM PRInt32 Find( const PRUnichar* aString, PRInt32 aOffset=0, PRInt32 aCount=-1 ) const;
  163. #endif
  164.  
  165.         
  166.         /**
  167.          * This methods scans the string backwards, looking for the given string
  168.          *
  169.          * @param   aString is substring to be sought in this
  170.          * @param   aIgnoreCase tells us whether or not to do caseless compare
  171.          * @param   aOffset tells us where in this string to start searching.
  172.          *          Use -1 to search from the end of the string.
  173.          * @param   aCount tells us how many iterations to make starting at the
  174.          *          given offset.
  175.          * @return  offset in string, or kNotFound
  176.          */
  177.  
  178.       NS_COM PRInt32 RFind( const nsCString& aString, PRBool aIgnoreCase=PR_FALSE, PRInt32 aOffset=-1, PRInt32 aCount=-1 ) const;
  179.       NS_COM PRInt32 RFind( const char* aCString, PRBool aIgnoreCase=PR_FALSE, PRInt32 aOffset=-1, PRInt32 aCount=-1 ) const;
  180.  
  181. #ifdef CharT_is_PRUnichar
  182.       NS_COM PRInt32 RFind( const nsAFlatString& aString, PRInt32 aOffset=-1, PRInt32 aCount=-1 ) const;
  183.       NS_COM PRInt32 RFind( const PRUnichar* aString, PRInt32 aOffset=-1, PRInt32 aCount=-1 ) const;
  184. #endif
  185.  
  186.  
  187.         /**
  188.          *  Search for given char within this string
  189.          *  
  190.          *  @param   aChar is the character to search for
  191.          *  @param   aOffset tells us where in this string to start searching
  192.          *  @param   aCount tells us how far from the offset we are to search.
  193.          *           Use -1 to search the whole string.
  194.          *  @return  offset in string, or kNotFound
  195.          */
  196.  
  197.       // PRInt32 FindChar( PRUnichar aChar, PRInt32 aOffset=0, PRInt32 aCount=-1 ) const;
  198.       NS_COM PRInt32 RFindChar( PRUnichar aChar, PRInt32 aOffset=-1, PRInt32 aCount=-1 ) const;
  199.  
  200.  
  201.         /**
  202.          * This method searches this string for the first character found in
  203.          * the given string.
  204.          *
  205.          * @param aString contains set of chars to be found
  206.          * @param aOffset tells us where in this string to start searching
  207.          *        (counting from left)
  208.          * @return offset in string, or kNotFound
  209.          */
  210.  
  211.       NS_COM PRInt32 FindCharInSet( const char* aString, PRInt32 aOffset=0 ) const;
  212.       PRInt32 FindCharInSet( const self_type& aString, PRInt32 aOffset=0 ) const
  213.         {
  214.           return FindCharInSet(aString.get(), aOffset);
  215.         }
  216.  
  217. #ifdef CharT_is_PRUnichar
  218.       NS_COM PRInt32 FindCharInSet( const PRUnichar* aString, PRInt32 aOffset=0 ) const;
  219. #endif
  220.  
  221.  
  222.         /**
  223.          * This method searches this string for the last character found in
  224.          * the given string.
  225.          *
  226.          * @param aString contains set of chars to be found
  227.          * @param aOffset tells us where in this string to start searching
  228.          *        (counting from left)
  229.          * @return offset in string, or kNotFound
  230.          */
  231.  
  232.       NS_COM PRInt32 RFindCharInSet( const char_type* aString, PRInt32 aOffset=-1 ) const;
  233.       PRInt32 RFindCharInSet( const self_type& aString, PRInt32 aOffset=-1 ) const
  234.         {
  235.           return RFindCharInSet(aString.get(), aOffset);
  236.         }
  237.  
  238.  
  239.         /**
  240.          * Compares a given string to this string. 
  241.          *
  242.          * @param   aString is the string to be compared
  243.          * @param   aIgnoreCase tells us how to treat case
  244.          * @param   aCount tells us how many chars to compare
  245.          * @return  -1,0,1
  246.          */
  247.  
  248. #ifdef CharT_is_char
  249.       NS_COM PRInt32 Compare( const char* aString, PRBool aIgnoreCase=PR_FALSE, PRInt32 aCount=-1 ) const;
  250. #endif
  251.  
  252.  
  253.         /**
  254.          * Equality check between given string and this string.
  255.          *
  256.          * @param   aString is the string to check
  257.          * @param   aIgnoreCase tells us how to treat case
  258.          * @param   aCount tells us how many chars to compare
  259.          * @return  boolean
  260.          */
  261. #ifdef CharT_is_char
  262.       PRBool EqualsIgnoreCase( const char* aString, PRInt32 aCount=-1 ) const {
  263.         return Compare(aString, PR_TRUE, aCount) == 0;
  264.       }
  265. #else
  266.       NS_COM PRBool EqualsIgnoreCase( const char* aString, PRInt32 aCount=-1 ) const;
  267.  
  268.  
  269.         /**
  270.          * Copies data from internal buffer onto given char* buffer
  271.          *
  272.          * NOTE: This only copies as many chars as will fit in given buffer (clips)
  273.          * @param aBuf is the buffer where data is stored
  274.          * @param aBuflength is the max # of chars to move to buffer
  275.          * @param aOffset is the offset to copy from
  276.          * @return ptr to given buffer
  277.          */
  278.  
  279.       NS_COM char* ToCString( char* aBuf, PRUint32 aBufLength, PRUint32 aOffset=0 ) const;
  280.  
  281. #endif // !CharT_is_PRUnichar
  282.  
  283.         /**
  284.          * Perform string to float conversion.
  285.          *
  286.          * @param   aErrorCode will contain error if one occurs
  287.          * @return  float rep of string value
  288.          */
  289.       NS_COM float ToFloat( PRInt32* aErrorCode ) const;
  290.  
  291.  
  292.         /**
  293.          * Perform string to int conversion.
  294.          * @param   aErrorCode will contain error if one occurs
  295.          * @param   aRadix tells us which radix to assume; kAutoDetect tells us to determine the radix for you.
  296.          * @return  int rep of string value, and possible (out) error code
  297.          */
  298.       NS_COM PRInt32 ToInteger( PRInt32* aErrorCode, PRUint32 aRadix=kRadix10 ) const;
  299.       
  300.  
  301.         /**
  302.          * |Left|, |Mid|, and |Right| are annoying signatures that seem better almost
  303.          * any _other_ way than they are now.  Consider these alternatives
  304.          * 
  305.          * aWritable = aReadable.Left(17);   // ...a member function that returns a |Substring|
  306.          * aWritable = Left(aReadable, 17);  // ...a global function that returns a |Substring|
  307.          * Left(aReadable, 17, aWritable);   // ...a global function that does the assignment
  308.          * 
  309.          * as opposed to the current signature
  310.          * 
  311.          * aReadable.Left(aWritable, 17);    // ...a member function that does the assignment
  312.          * 
  313.          * or maybe just stamping them out in favor of |Substring|, they are just duplicate functionality
  314.          *         
  315.          * aWritable = Substring(aReadable, 0, 17);
  316.          */
  317.  
  318.       NS_COM size_type Mid( self_type& aResult, PRUint32 aStartPos, PRUint32 aCount ) const;
  319.  
  320.       size_type Left( self_type& aResult, size_type aCount ) const
  321.         {
  322.           return Mid(aResult, 0, aCount);
  323.         }
  324.  
  325.       size_type Right( self_type& aResult, size_type aCount ) const
  326.         {
  327.           aCount = NS_MIN(mLength, aCount);
  328.           return Mid(aResult, mLength - aCount, aCount);
  329.         }
  330.  
  331.  
  332.         /**
  333.          * Set a char inside this string at given index
  334.          *
  335.          * @param aChar is the char you want to write into this string
  336.          * @param anIndex is the ofs where you want to write the given char
  337.          * @return TRUE if successful
  338.          */
  339.  
  340.       NS_COM PRBool SetCharAt( PRUnichar aChar, PRUint32 aIndex );
  341.  
  342.  
  343.         /**
  344.          *  These methods are used to remove all occurances of the
  345.          *  characters found in aSet from this string.
  346.          *  
  347.          *  @param  aSet -- characters to be cut from this
  348.          */
  349.       NS_COM void StripChars( const char* aSet );
  350.  
  351.  
  352.         /**
  353.          *  This method strips whitespace throughout the string.
  354.          */
  355.       NS_COM void StripWhitespace();
  356.  
  357.  
  358.         /**
  359.          *  swaps occurence of 1 string for another
  360.          */
  361.  
  362.       NS_COM void ReplaceChar( char_type aOldChar, char_type aNewChar );
  363.       NS_COM void ReplaceChar( const char* aSet, char_type aNewChar );
  364.       NS_COM void ReplaceSubstring( const self_type& aTarget, const self_type& aNewValue);
  365.       NS_COM void ReplaceSubstring( const char_type* aTarget, const char_type* aNewValue);
  366.  
  367.  
  368.         /**
  369.          *  This method trims characters found in aTrimSet from
  370.          *  either end of the underlying string.
  371.          *  
  372.          *  @param   aSet -- contains chars to be trimmed from both ends
  373.          *  @param   aEliminateLeading
  374.          *  @param   aEliminateTrailing
  375.          *  @param   aIgnoreQuotes -- if true, causes surrounding quotes to be ignored
  376.          *  @return  this
  377.          */
  378.       NS_COM void Trim( const char* aSet, PRBool aEliminateLeading=PR_TRUE, PRBool aEliminateTrailing=PR_TRUE, PRBool aIgnoreQuotes=PR_FALSE );
  379.  
  380.         /**
  381.          *  This method strips whitespace from string.
  382.          *  You can control whether whitespace is yanked from start and end of
  383.          *  string as well.
  384.          *  
  385.          *  @param   aEliminateLeading controls stripping of leading ws
  386.          *  @param   aEliminateTrailing controls stripping of trailing ws
  387.          */
  388.       NS_COM void CompressWhitespace( PRBool aEliminateLeading=PR_TRUE, PRBool aEliminateTrailing=PR_TRUE );
  389.  
  390.  
  391.         /**
  392.          * assign/append/insert with _LOSSY_ conversion
  393.          */
  394.  
  395.       NS_COM void AssignWithConversion( const nsTAString_IncompatibleCharT& aString );
  396.       NS_COM void AssignWithConversion( const incompatible_char_type* aData, PRInt32 aLength=-1 );
  397.  
  398.       NS_COM void AppendWithConversion( const nsTAString_IncompatibleCharT& aString );
  399.       NS_COM void AppendWithConversion( const incompatible_char_type* aData, PRInt32 aLength=-1 );
  400.  
  401.         /**
  402.          * Append the given integer to this string 
  403.          */
  404.       NS_COM void AppendInt( PRInt32 aInteger, PRInt32 aRadix=kRadix10 ); //radix=8,10 or 16
  405.  
  406.         /**
  407.          * Append the given unsigned integer to this string
  408.          */
  409.       inline void AppendInt( PRUint32 aInteger, PRInt32 aRadix = kRadix10 )
  410.         {
  411.           AppendInt(PRInt32(aInteger), aRadix);
  412.         }
  413.  
  414.         /**
  415.          * Append the given 64-bit integer to this string.
  416.          * @param aInteger The integer to append
  417.          * @param aRadix   The radix to use; can be 8, 10 or 16.
  418.          */
  419.       NS_COM void AppendInt( PRInt64 aInteger, PRInt32 aRadix=kRadix10 );
  420.  
  421.         /**
  422.          * Append the given float to this string 
  423.          */
  424.  
  425.       NS_COM void AppendFloat( double aFloat );
  426.  
  427. #endif // !MOZ_STRING_WITH_OBSOLETE_API
  428.  
  429.  
  430.     protected:
  431.  
  432.       explicit
  433.       nsTString_CharT( PRUint32 flags )
  434.         : substring_type(flags) {}
  435.  
  436.         // allow subclasses to initialize fields directly
  437.       nsTString_CharT( char_type* data, size_type length, PRUint32 flags )
  438.         : substring_type(data, length, flags) {}
  439.   };
  440.  
  441.  
  442. class nsTFixedString_CharT : public nsTString_CharT
  443.   {
  444.     public:
  445.  
  446.       typedef nsTFixedString_CharT    self_type;
  447.       typedef nsTFixedString_CharT    fixed_string_type;
  448.  
  449.     public:
  450.  
  451.         /**
  452.          * @param data
  453.          *        fixed-size buffer to be used by the string (the contents of
  454.          *        this buffer may be modified by the string)
  455.          * @param storageSize
  456.          *        the size of the fixed buffer
  457.          * @param length (optional)
  458.          *        the length of the string already contained in the buffer
  459.          */
  460.  
  461.       nsTFixedString_CharT( char_type* data, size_type storageSize )
  462.         : string_type(data, char_traits::length(data), F_TERMINATED | F_FIXED | F_CLASS_FIXED)
  463.         , mFixedCapacity(storageSize - 1)
  464.         , mFixedBuf(data)
  465.         {}
  466.  
  467.       nsTFixedString_CharT( char_type* data, size_type storageSize, size_type length )
  468.         : string_type(data, length, F_TERMINATED | F_FIXED | F_CLASS_FIXED)
  469.         , mFixedCapacity(storageSize - 1)
  470.         , mFixedBuf(data)
  471.         {
  472.           // null-terminate
  473.           mFixedBuf[length] = char_type(0);
  474.         }
  475.  
  476.         // |operator=| does not inherit, so we must define our own
  477.       self_type& operator=( char_type c )                                                       { Assign(c);        return *this; }
  478.       self_type& operator=( const char_type* data )                                             { Assign(data);     return *this; }
  479.       self_type& operator=( const substring_type& str )                                         { Assign(str);      return *this; }
  480.       self_type& operator=( const substring_tuple_type& tuple )                                 { Assign(tuple);    return *this; }
  481. #ifdef MOZ_V1_STRING_ABI
  482.       self_type& operator=( const abstract_string_type& readable )                              { Assign(readable); return *this; }
  483. #endif
  484.  
  485.     protected:
  486.  
  487.       friend class nsTSubstring_CharT;
  488.  
  489.       size_type  mFixedCapacity;
  490.       char_type *mFixedBuf;
  491.   };
  492.  
  493.  
  494.   /**
  495.    * nsTAutoString_CharT
  496.    *
  497.    * Subclass of nsTString_CharT that adds support for stack-based string
  498.    * allocation.  Do not allocate this class on the heap! ;-)
  499.    */
  500. class nsTAutoString_CharT : public nsTFixedString_CharT
  501.   {
  502.     public:
  503.  
  504.       typedef nsTAutoString_CharT    self_type;
  505.  
  506.     public:
  507.  
  508.         /**
  509.          * constructors
  510.          */
  511.  
  512.       nsTAutoString_CharT()
  513.         : fixed_string_type(mStorage, kDefaultStorageSize, 0)
  514.         {}
  515.  
  516.       explicit
  517.       nsTAutoString_CharT( char_type c )
  518.         : fixed_string_type(mStorage, kDefaultStorageSize, 0)
  519.         {
  520.           Assign(c);
  521.         }
  522.  
  523.       explicit
  524.       nsTAutoString_CharT( const char_type* data, size_type length = size_type(-1) )
  525.         : fixed_string_type(mStorage, kDefaultStorageSize, 0)
  526.         {
  527.           Assign(data, length);
  528.         }
  529.  
  530.       nsTAutoString_CharT( const self_type& str )
  531.         : fixed_string_type(mStorage, kDefaultStorageSize, 0)
  532.         {
  533.           Assign(str);
  534.         }
  535.  
  536.       explicit
  537.       nsTAutoString_CharT( const substring_type& str )
  538.         : fixed_string_type(mStorage, kDefaultStorageSize, 0)
  539.         {
  540.           Assign(str);
  541.         }
  542.  
  543.       nsTAutoString_CharT( const substring_tuple_type& tuple )
  544.         : fixed_string_type(mStorage, kDefaultStorageSize, 0)
  545.         {
  546.           Assign(tuple);
  547.         }
  548.  
  549. #ifdef MOZ_V1_STRING_ABI
  550.       explicit
  551.       nsTAutoString_CharT( const abstract_string_type& readable )
  552.         : fixed_string_type(mStorage, kDefaultStorageSize, 0)
  553.         {
  554.           Assign(readable);
  555.         }
  556. #endif
  557.  
  558.         // |operator=| does not inherit, so we must define our own
  559.       self_type& operator=( char_type c )                                                       { Assign(c);        return *this; }
  560.       self_type& operator=( const char_type* data )                                             { Assign(data);     return *this; }
  561.       self_type& operator=( const self_type& str )                                              { Assign(str);      return *this; }
  562.       self_type& operator=( const substring_type& str )                                         { Assign(str);      return *this; }
  563.       self_type& operator=( const substring_tuple_type& tuple )                                 { Assign(tuple);    return *this; }
  564. #ifdef MOZ_V1_STRING_ABI
  565.       self_type& operator=( const abstract_string_type& readable )                              { Assign(readable); return *this; }
  566. #endif
  567.  
  568.       enum { kDefaultStorageSize = 64 };
  569.  
  570.     private:
  571.  
  572.       char_type mStorage[kDefaultStorageSize];
  573.   };
  574.  
  575.  
  576.   /**
  577.    * nsTXPIDLString extends nsTString such that:
  578.    *
  579.    *   (1) mData can be null
  580.    *   (2) objects of this type can be automatically cast to |const CharT*|
  581.    *   (3) getter_Copies method is supported to adopt data
  582.    */
  583. class nsTXPIDLString_CharT : public nsTString_CharT
  584.   {
  585.     public:
  586.  
  587.       typedef nsTXPIDLString_CharT    self_type;
  588.  
  589.     public:
  590.  
  591.       nsTXPIDLString_CharT()
  592.         : string_type(NS_CONST_CAST(char_type*, char_traits::sEmptyBuffer), 0, F_TERMINATED | F_VOIDED) {}
  593.  
  594.         // copy-constructor required to avoid default
  595.       nsTXPIDLString_CharT( const self_type& str )
  596.         : string_type(NS_CONST_CAST(char_type*, char_traits::sEmptyBuffer), 0, F_TERMINATED | F_VOIDED)
  597.         {
  598.           Assign(str);
  599.         }
  600.  
  601.         // return nsnull if we are voided
  602.       const char_type* get() const
  603.         {
  604.           return (mFlags & F_VOIDED) ? nsnull : mData;
  605.         }
  606.  
  607.         // this case operator is the reason why this class cannot just be a
  608.         // typedef for nsTString
  609.       operator const char_type*() const
  610.         {
  611.           return get();
  612.         }
  613.  
  614.         // need this to diambiguous operator[int]
  615.       char_type operator[]( PRInt32 i ) const
  616.         {
  617.           return CharAt(index_type(i));
  618.         }
  619.  
  620.         // |operator=| does not inherit, so we must define our own
  621.       self_type& operator=( char_type c )                                                       { Assign(c);        return *this; }
  622.       self_type& operator=( const char_type* data )                                             { Assign(data);     return *this; }
  623.       self_type& operator=( const self_type& str )                                              { Assign(str);      return *this; }
  624.       self_type& operator=( const substring_type& str )                                         { Assign(str);      return *this; }
  625.       self_type& operator=( const substring_tuple_type& tuple )                                 { Assign(tuple);    return *this; }
  626. #ifdef MOZ_V1_STRING_ABI
  627.       self_type& operator=( const abstract_string_type& readable )                              { Assign(readable); return *this; }
  628. #endif
  629.   };
  630.  
  631.  
  632.   /**
  633.    * getter_Copies support for use with raw string out params:
  634.    *
  635.    *    NS_IMETHOD GetBlah(char**);
  636.    *    
  637.    *    void some_function()
  638.    *    {
  639.    *      nsXPIDLCString blah;
  640.    *      GetBlah(getter_Copies(blah));
  641.    *      // ...
  642.    *    }
  643.    */
  644. class nsTGetterCopies_CharT
  645.   {
  646.     public:
  647.       typedef CharT char_type;
  648.  
  649.       nsTGetterCopies_CharT(nsTXPIDLString_CharT& str)
  650.         : mString(str), mData(nsnull) {}
  651.  
  652.       ~nsTGetterCopies_CharT()
  653.         {
  654.           mString.Adopt(mData); // OK if mData is null
  655.         }
  656.  
  657.       operator char_type**()
  658.         {
  659.           return &mData;
  660.         }
  661.  
  662.     private:
  663.       nsTXPIDLString_CharT& mString;
  664.       char_type*            mData;
  665.   };
  666.  
  667. inline
  668. nsTGetterCopies_CharT
  669. getter_Copies( nsTXPIDLString_CharT& aString )
  670.   {
  671.     return nsTGetterCopies_CharT(aString);
  672.   }
  673.  
  674.  
  675.   /**
  676.    * nsTAdoptingString extends nsTXPIDLString such that:
  677.    *
  678.    * (1) Adopt given string on construction or assignment, i.e. take
  679.    * the value of what's given, and make what's given forget its
  680.    * value. Note that this class violates constness in a few
  681.    * places. Be careful!
  682.    */
  683. class nsTAdoptingString_CharT : public nsTXPIDLString_CharT
  684.   {
  685.     public:
  686.  
  687.       typedef nsTAdoptingString_CharT    self_type;
  688.  
  689.     public:
  690.  
  691.       explicit nsTAdoptingString_CharT() {}
  692.       explicit nsTAdoptingString_CharT(char_type* str, size_type length = size_type(-1))
  693.         {
  694.           Adopt(str, length);
  695.         }
  696.  
  697.         // copy-constructor required to adopt on copy. Note that this
  698.         // will violate the constness of |str| in the operator=()
  699.         // call. |str| will be truncated as a side-effect of this
  700.         // constructor.
  701.       nsTAdoptingString_CharT( const self_type& str )
  702.         {
  703.           *this = str;
  704.         }
  705.  
  706.         // |operator=| does not inherit, so we must define our own
  707.       self_type& operator=( const substring_type& str )                                         { Assign(str);      return *this; }
  708.       self_type& operator=( const substring_tuple_type& tuple )                                 { Assign(tuple);    return *this; }
  709. #ifdef MOZ_V1_STRING_ABI
  710.       self_type& operator=( const abstract_string_type& readable )                              { Assign(readable); return *this; }
  711. #endif
  712.  
  713.         // Adopt(), if possible, when assigning to a self_type&. Note
  714.         // that this violates the constness of str, str is always
  715.         // truncated when this operator is called.
  716.       NS_COM self_type& operator=( const self_type& str );
  717.  
  718.     private:
  719.         // NOT TO BE IMPLEMENTED.
  720.       self_type& operator=( const char_type* data );
  721.       self_type& operator=( char_type* data );
  722.   };
  723.  
  724.